<script setup lang="ts">
import type { MultiSelectorPickerOnChange, SelectorPickerOnChange } from '@uni-helper/uni-app-types'
import mpHtml from '@/common/components/mp-html/mp-html.vue'
import { useUploadFile } from '@/common/composables/useUpload'

const props = defineProps<{
  content: string
}>()

const emits = defineEmits(['update:content', 'onClear'])

/** html ref 实例 */
const htmlRef = ref()

/** 是否是可编辑的 */
const isEditable = ref(true)

const { uploadFile } = useUploadFile()

/** 保存内容 */
const onChange = () => {
  console.log('onChange')
  // 获取富文本的值
  const content = htmlRef.value.getContent()
  console.log('content', content)

  // 触发事件 同步父组件的content值
  emits('update:content', content)
}

/** 清空内容 */
const clearContent = () => {
  uni.showModal({
    title: '温馨提示',
    content: '您确定要清空内容吗?',
    success: (success) => {
      if (success.confirm) {
        htmlRef.value.clear()
        // 触发事件 同步父组件的content值
        emits('update:content', '')
      }
    },
  })
}

/** 插入标题 */
const insertHeader = () => {
  // 弹出操作表 让用户选择标题的大小
  uni.showActionSheet({
    itemList: ['大标题', '中标题', '小标题'],
    success: (success) => {
      // 获取对应的标签名
      const tagName = ['h1', 'h3', 'h5'][success.tapIndex]
      // 调用实例的 insertHtml 插入标题
      htmlRef.value.insertHtml(`<${tagName}>标题</${tagName}>`)

      // 保存获取内容
      onChange()
    },
  })
}

/** 插入列表 */
const insertList = () => {
  /** 根据 type & count 渲染列表项 */
  const render = (type: number, count: number) => {
    let liStr = ''
    Array.from({ length: count + 1 }).forEach((item, index) => {
      return liStr += `<li>列表项 - ${index + 1}</li>`
    })

    switch (type) {
      case 0:
        htmlRef.value.insertHtml(`
          <ol>
          ${liStr}
          </ol>
          `)
        break
      case 1:
        htmlRef.value.insertHtml(`
          <ul>
          ${liStr}
          </ul>
          `)
        break
    }
  }

  /** 弹出选择 列表类型操作项 */
  uni.showActionSheet({
    itemList: ['有序列表', '无序列表'],
    success: (success) => {
      /** 选择列表项数量 */
      uni.showActionSheet({
        itemList: ['1', '2', '3', '4', '5'],
        success: (count) => {
          // 渲染列表
          render(success.tapIndex, count.tapIndex)
          // 保存获取内容
          onChange()
        },
      })
    },
  })
}

/** 插入内容 */
const edit = (e: any) => {
  const dataset = e.currentTarget.dataset
  htmlRef.value[dataset.method](dataset.param)

  // 保存获取内容
  onChange()
}

/**
 * 表格选择 popup
 */
const tablePopupRef = ref()

/** table 列数行数 */
const tableColsRows = ref({
  columns: 2,
  rows: 1,
})

/** 插入表格 */
const insertTable = () => {
  tablePopupRef.value.close()

  htmlRef.value.insertTable(tableColsRows.value.rows, tableColsRows.value.columns)
}

/** 修改表格的列行 */
const pickerChange: MultiSelectorPickerOnChange = (e) => {
  if (!e.currentTarget?.dataset)
    return

  const type = e.currentTarget.dataset.type

  if (type === 'cols') {
    tableColsRows.value.columns = Number(e.detail.value)
  }
  else {
    tableColsRows.value.rows = Number(e.detail.value)
  }
}

const remove = () => {
  console.log('删除图片')
}

// 暴露组件方法
defineExpose({
  onChange,
})
onReady(() => {
  // 需要在初始时给组件设置一个 getSrc 方法（否则插入图片、音视频、链接或修改链接等操作无法使用）每次组件内需要链接时会调用此方法 返回线上地址即可
  // https://jin-yufeng.github.io/mp-html/#/advanced/plugin?id=editable_demo
  htmlRef.value.getSrc = (type: string) => {
    return new Promise((resolve) => {
      // 如果是插入图片
      if (type === 'img') {
        // 弹出操作菜单
        uni.showActionSheet({
          itemList: ['本地选取', '网络链接'],
          success: (success) => {
            // 本地选取
            if (success.tapIndex === 0) {
              uni.chooseImage({
                count: 1,
                success: async (success) => {
                  // uni.editImage({
                  //   src: success.tempFilePaths[0],
                  //   complete: (res) => {
                  //     console.log(res)
                  //   },
                  // })
                  const imgUrl = await uploadFile(success.tempFilePaths[0])

                  resolve(imgUrl)
                },
              })
            }
            else if (success.tapIndex === 1) {
              uni.showModal({
                title: '请输入网络图片连接',
                editable: true,
                success: (success) => {
                  if (success.confirm) {
                    resolve(success.content)
                  }
                },
              })
            }
          },
        })
      }
    })
  }
})
</script>

<template>
  <view class="editor-container">
    <view class="editor-operation">
      <image
        src="/static/icon/ic_undo.svg" alt="" class="editor-operation-icon" data-method="undo"
        @click="(e) => edit(e)"
      />
      <image
        src="/static/icon/ic_redo.svg" alt="" class="editor-operation-icon" data-method="redo"
        @click="(e) => edit(e)"
      />
      <image src="/static/icon/ic_heading.svg" alt="" class="editor-operation-icon" @click="insertHeader" />
      <image
        src="/static/icon/ic_type.svg" alt="" class="editor-operation-icon" data-method="insertText"
        @click="(e) => edit(e)"
      />
      <image src="/static/icon/ic_list.svg" alt="" class="editor-operation-icon" @click="insertList" />
      <image
        src="/static/icon/ic_image.svg" data-method="insertImg" alt="" class="editor-operation-icon"
        @click="(e) => edit(e)"
      />
      <image src="/static/icon/ic_table.svg" alt="" class="editor-operation-icon" @click="tablePopupRef.open()" />
      <image src="/static/icon/ic_delete.svg" alt="" class="editor-operation-icon" @click="clearContent" />
      <image src="/static/icon/ic_save.svg" alt="" class="editor-operation-icon" @click="onChange" />
    </view>
    <view class="editor-content-container">
      <mpHtml
        ref="htmlRef" domain="hope-mp.oss-cn-guangzhou.aliyuncs.com" :content="props.content"
        :editable="isEditable" lazy-load preview-img @remove="remove"
      />
    </view>

    <uni-popup ref="tablePopupRef" type="bottom" background-color="#ffffff">
      <view class="popup-table">
        <uni-section title="请选择行数和列数" title-font-size="36rpx" type="line" />
        <view class="popup-table-content">
          <picker
            class="popup-table-picker" :range="[1, 2, 3, 4, 5, 6, 7, 8, 9]" data-type="rows"
            @change="pickerChange"
          >
            {{ tableColsRows.rows }}
          </picker>
          <text class="popup-table-text">
            行
          </text>
          <picker class="popup-table-picker" :range="[2, 3, 4, 5]" data-type="cols" @change="pickerChange">
            {{ tableColsRows.columns }}
          </picker>
          <text class="popup-table-text">
            列
          </text>
        </view>

        <view @click="insertTable">
          <hope-button title="确定" />
        </view>
      </view>
    </uni-popup>
  </view>
</template>

<style scoped lang="scss">
.editor {
  &-operation {
    display: flex;
    gap: $padding-base;

    &-icon {
      width: 60rpx;
      height: 60rpx;
    }
  }

  &-content {
    &-container {
      padding: $padding-base;

    }
  }
}

.popup {
  &-table {
    display: flex;
    flex-direction: column;
    gap: $padding-base;
    padding: $padding-base;

    &-content {
      display: flex;
      justify-content: center;
    }

    &-picker {
      padding-inline: $padding-base;
      border-bottom: 1px solid $uni-text-color-grey;
      font-size: $font-size-lg;
    }

    &-text {
      font-size: $font-size-lg;
    }
  }
}
</style>
